<template>
  <div class="robot-container">
    <!-- 聊天头部 -->
    <div class="chat-header">
      <h2>智能客服</h2>
      <p>欢迎咨询BUO宠物生活馆</p>
    </div>

    <!-- 聊天消息区域 -->
    <div class="chat-messages" ref="messagesContainer">
      <!-- 系统欢迎消息 -->
      <div v-if="messages.length === 0" class="welcome-message">
        <p>你好！我是BUO宠物助手，很高兴为你服务。</p>
        <p>请问有什么可以帮助你的吗？</p>
      </div>

      <!-- 消息列表 -->
      <div
        v-for="(message, index) in messages"
        :key="index"
        :class="['message', message.type]"
      >
        <div class="message-avatar">
          <img :src="message.avatar" alt="头像" />
          <!-- 恢复为动态的message.avatar -->
        </div>
        <div class="message-content">
          <!-- 使用v-html渲染解析后的HTML -->
          <div class="message-text" v-html="parseMarkdown(message.text)"></div>
          <div class="message-time">{{ message.time }}</div>
        </div>
      </div>

      <!-- 正在输入提示 -->
      <div v-if="isTyping" class="typing-indicator">
        <div class="message-content">
          <div class="typing-dots">
            <span></span>
            <span></span>
            <span></span>
          </div>
        </div>
      </div>
    </div>

    <!-- 输入区域 -->
    <div class="chat-input">
      <input
        v-model="inputMessage"
        type="text"
        placeholder="请输入您的问题..."
        @keyup.enter="sendMessage"
        :disabled="isTyping"
      />
      <!-- 修改按钮，根据isTyping状态显示不同内容和执行不同操作 -->
      <button
        @click="isTyping ? stopGenerating() : sendMessage()"
        :disabled="!inputMessage.trim() && !isTyping"
        :class="{ 'stop-button': isTyping }"
      >
        {{ isTyping ? "停止回答" : "发送" }}
      </button>
    </div>
  </div>
</template>

<script setup>
import { ref, onMounted, nextTick, onUnmounted } from "vue";
import { useStore } from "vuex";

// 导入头像图片
const userAvatar = new URL(
  "../assets/image/default-avatar.png",
  import.meta.url
).href;
const robotAvatar = new URL("../assets/image/robot-avatar.png", import.meta.url)
  .href;

const store = useStore();
const messages = ref([]);
const inputMessage = ref("");
const isTyping = ref(false);
const messagesContainer = ref(null);
let currentBotMessage = null; // 当前机器人消息对象，用于流式更新
let controller = null; // AbortController，用于取消请求

// 简单的Markdown解析函数
const parseMarkdown = (text) => {
  if (!text) return "";
  let parsed = text
    // 处理标题 ###
    .replace(/### (.*?)(?=\n|$)/g, '<h3 class="markdown-h3">$1</h3>')
    // 处理加粗 **文本**
    .replace(/\*\*(.*?)\*\*/g, "<strong>$1</strong>")
    .replace(/\n/g, "<br>");
  return parsed;
};

// 获取当前时间
const getCurrentTime = () => {
  const now = new Date();
  const hours = now.getHours().toString().padStart(2, "0");
  const minutes = now.getMinutes().toString().padStart(2, "0");
  return `${hours}:${minutes}`;
};

// 滚动到底部
const scrollToBottom = () => {
  nextTick(() => {
    if (messagesContainer.value) {
      messagesContainer.value.scrollTop = messagesContainer.value.scrollHeight;
    }
  });
};

// 停止生成回答的函数
const stopGenerating = () => {
  if (controller) {
    controller.abort(); // 取消当前请求
    console.log("已停止生成回答");
  }
  // 重置状态
  isTyping.value = false;
  currentBotMessage = null;
};

// 发送消息
const sendMessage = async () => {
  const text = inputMessage.value.trim();
  if (!text || isTyping.value) return;

  // 取消之前可能存在的请求
  if (controller) {
    controller.abort();
  }
  controller = new AbortController();

  // 添加用户消息
  messages.value.push({
    type: "user",
    text,
    time: getCurrentTime(),
    avatar: userAvatar,
  });

  inputMessage.value = "";
  scrollToBottom();

  // 显示正在输入
  isTyping.value = true;

  try {
    // 创建机器人消息对象（初始为空）
    currentBotMessage = {
      type: "bot",
      text: "",
      time: getCurrentTime(),
      avatar: robotAvatar,
    };
    messages.value.push(currentBotMessage);

    // 发送请求到后端API
    const response = await fetch("http://localhost:8000/api/llm/chat/", {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        // 如果需要认证，可以添加token
        // 'Authorization': `Bearer ${store.state.user.token}`
      },
      body: JSON.stringify({
        message: text,
        user_id: store.getters["user/isLoggedIn"]
          ? store.state.user.user.id
          : "123456",
      }),
      signal: controller.signal,
    });

    if (!response.ok) {
      throw new Error(`HTTP error! status: ${response.status}`);
    }

    // 处理流式响应
    const reader = response.body.getReader();
    const decoder = new TextDecoder();

    while (true) {
      const { done, value } = await reader.read();
      if (done) {
        break;
      }

      // 解码接收到的数据
      const chunk = decoder.decode(value, { stream: true });
      // 分割多行消息
      const lines = chunk.split("\n");

      for (const line of lines) {
        if (line.startsWith("data: ")) {
          const data = line.substring(6).trim();
          if (data === "[DONE]") {
            break;
          }

          try {
            // 解析JSON数据
            const parsedData = JSON.parse(data);

            if (parsedData.type === "content" && parsedData.content) {
              // 更新机器人消息内容
              currentBotMessage.text += parsedData.content;
              // 触发Vue响应式更新
              messages.value = [...messages.value];
              scrollToBottom();
            } else if (parsedData.type === "error") {
              // 处理错误信息
              currentBotMessage.text = `抱歉，发生错误：${parsedData.error}`;
              messages.value = [...messages.value];
            } else if (parsedData.type === "done") {
              // 响应完成
              console.log("响应完成");
            } else if (
              parsedData.type === "metadata" &&
              parsedData.token_usage
            ) {
              // 可以在这里记录token使用量
              console.log("Token usage:", parsedData.token_usage);
            }
          } catch (error) {
            console.error("解析JSON失败:", error);
          }
        }
      }
    }
  } catch (error) {
    if (error.name !== "AbortError") {
      console.error("请求失败:", error);
      // 如果当前有机器人消息但内容为空，添加错误信息
      if (currentBotMessage && currentBotMessage.text === "") {
        currentBotMessage.text = "抱歉，无法连接到AI服务，请稍后再试。";
        messages.value = [...messages.value];
      }
    }
  } finally {
    // 隐藏正在输入状态
    isTyping.value = false;
    currentBotMessage = null;
    scrollToBottom();
  }
};

// 组件挂载时初始化
onMounted(() => {
  scrollToBottom();
});

// 组件卸载时清理资源
onUnmounted(() => {
  if (controller) {
    controller.abort();
  }
});
</script>

<style lang="less">
.robot-container {
  display: flex;
  flex-direction: column;
  height: 100vh;
  background-color: #f5f5f5;
}

.chat-header {
  background: linear-gradient(135deg, #8d26e6, #2a6cff);
  color: white;
  padding: 20px;
  text-align: center;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}

.chat-header h2 {
  margin: 0 0 8px 0;
  font-size: 24px;
  font-weight: 600;
}

.chat-header p {
  margin: 0;
  font-size: 14px;
  opacity: 0.9;
}

.chat-messages {
  flex: 1;
  overflow-y: auto;
  padding: 20px;
  display: flex;
  flex-direction: column;
  gap: 16px;
}

.welcome-message {
  background: white;
  border-radius: 12px;
  padding: 20px;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);
  align-self: center;
  max-width: 60%;
  text-align: center;
  color: #666;
  font-size: 16px;
}

.welcome-message p {
  margin: 8px 0;
}

.message {
  display: flex;
  gap: 12px;
  align-items: flex-start;
}

.message.user {
  flex-direction: row-reverse;
}

.message-avatar {
  width: 40px;
  height: 40px;
  border-radius: 50%;
  overflow: hidden;
  flex-shrink: 0;
}

.message-avatar img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.message-content {
  max-width: 60%;
}

.message-text {
  padding: 12px 16px;
  border-radius: 18px;
  word-wrap: break-word;
  font-size: 15px;
  line-height: 1.4;
}

/* 添加Markdown样式 */
.message-text :deep(.markdown-h3) {
  margin: 10px 0 8px 0;
  font-size: 16px;
  font-weight: 600;
  color: #333;
}

.message-text :deep(strong) {
  font-weight: 600;
  color: #2a6cff;
}

.message.user .message-text {
  background: #2a6cff;
  color: white;
  border-bottom-right-radius: 6px;
}

.message.bot .message-text {
  background: white;
  color: #333;
  border-bottom-left-radius: 6px;
  box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
}

.message-time {
  font-size: 12px;
  color: #999;
  margin-top: 4px;
  text-align: right;
}

.message.bot .message-time {
  text-align: left;
}

.typing-indicator {
  display: flex;
  gap: 12px;
  align-items: flex-start;
}

.typing-dots {
  display: flex;
  gap: 4px;
  padding: 12px 16px;
  background: white;
  border-radius: 18px;
  border-bottom-left-radius: 6px;
}

.typing-dots span {
  width: 6px;
  height: 6px;
  background: #999;
  border-radius: 50%;
  animation: typing 1.4s infinite ease-in-out both;
}

.typing-dots span:nth-child(1) {
  animation-delay: -0.32s;
}

.typing-dots span:nth-child(2) {
  animation-delay: -0.16s;
}

@keyframes typing {
  0%,
  80%,
  100% {
    transform: scale(0);
  }
  40% {
    transform: scale(1);
  }
}

.chat-input {
  display: flex;
  gap: 12px;
  padding: 20px;
  background: white;
  border-top: 1px solid #eee;
  box-shadow: 0 -2px 8px rgba(0, 0, 0, 0.05);
}

.chat-input input {
  flex: 1;
  padding: 12px 16px;
  border: 1px solid #ddd;
  border-radius: 24px;
  font-size: 15px;
  outline: none;
  transition: border-color 0.2s;
}

.chat-input input:focus {
  border-color: #2a6cff;
}

.chat-input input:disabled {
  background: #f9f9f9;
  cursor: not-allowed;
}

.chat-input button {
  padding: 12px 24px;
  background: #2a6cff;
  color: white;
  border: none;
  border-radius: 24px;
  font-size: 15px;
  font-weight: 500;
  cursor: pointer;
  transition: background 0.2s;
  white-space: nowrap;
}

.chat-input button:hover:not(:disabled) {
  background: #1e56e8;
}

.chat-input button:disabled {
  background: #ccc;
  cursor: not-allowed;
}

/* 响应式设计 */
@media (max-width: 768px) {
  .message-content {
    max-width: 75%;
  }

  .chat-header {
    padding: 16px;
  }

  .chat-header h2 {
    font-size: 20px;
  }

  .chat-messages {
    padding: 16px;
  }

  .chat-input {
    padding: 16px;
  }
}

/* 在style标签内添加以下样式 */
.chat-input button.stop-button {
  background: #ff6b6b;
}

.chat-input button.stop-button:hover {
  background: #ee5253;
}
</style>
